{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "slide"
    }
   },
   "source": [
    "## Kotlin Technology Sharing\n",
    "\n",
    "\n",
    "\n",
    " **Author  :   蔡海飞  **  \n",
    " **Date      :    2018/1/XX**\n",
    "\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "slide"
    }
   },
   "source": [
    "## Introduration\n",
    "\n",
    "- 时间线\n",
    "- Koltin的应用\n",
    "- 为什么使用kotlin ?\n",
    "- Kotlin与Java\n",
    "- Kotlin的特性"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 时间线\n",
    "\n",
    "- July 18,2011  \n",
    "  Kotlin 于2011年7月18日在Jvm language Commit 会议中被JetBrains公布\n",
    "\n",
    "- August 3, 2011  \n",
    "   JetBrains 公布Kotlin 事件跟踪器\n",
    "   \n",
    "- January 10,2012  \n",
    "  Kotlin公开预览版\n",
    "  \n",
    "- February 14,2012  \n",
    "   Kotlin 开放源代码( http://github.com/JetBrains/Kotlin)\n",
    " \n",
    " \n",
    "- October 10,2012\n",
    "   Kotlin 网络研讨会\n",
    "   \n",
    "   \n",
    "- December 11,2012  \n",
    "   kotlin M4完成\n",
    "   \n",
    "- August 12,2013  \n",
    "   Android studio支持kotlin插件\n",
    "   \n",
    "  \n",
    "- May 18,2017  \n",
    "  Google IO宣布kotlin为android开发官方语言,并且Android studio 3开始内嵌kotlin支持.\n",
    "  "
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "slide"
    }
   },
   "source": [
    "## Kotlin 的使用场景\n",
    "\n",
    "-  服务器端开发\n",
    "- Android端开发\n",
    "- 浏览器端开发\n",
    "- 原生开发\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "slide"
    }
   },
   "source": [
    "##  为什么使用kotlin ?\n",
    "\n",
    "-  **代码简洁**  \n",
    "    Kotlin的代码结构简单，支持lambda表达式，语法结构更加通俗易读.\n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "subslide"
    }
   },
   "source": [
    "\n",
    "#### POJO的实现\n",
    "```java\n",
    "//java的实现\n",
    "public class  UserInfo{\n",
    "    private String name;\n",
    "    private String pwd;\n",
    "\n",
    "    pulblic void setName(String name){\n",
    "        this.name=name;\n",
    "    }\n",
    "    \n",
    "    public String getName(){\n",
    "        return name;\n",
    "    }\n",
    "    \n",
    "    public void setPwd(String pwd){\n",
    "        this.pwd=pwd;\n",
    "    }\n",
    "    \n",
    "    public String getPwd(){\n",
    "        return pwd;\n",
    "    }\n",
    "    ......\n",
    "}\n",
    "\n",
    "```\n",
    "\n",
    "\n",
    "```kotlin\n",
    "//kotlin的实现\n",
    "data class UserInfo(var name:String,var pwd:String)\n",
    "```\n",
    "\n",
    "\n",
    "#### 单例模式\n",
    "\n",
    "```kotlin\n",
    "\n",
    "//关键字object 可创建一个单例模式的类，可以直接使用Singleton调用，无构造函数.\n",
    "object Singleton {\n",
    "      val tag: String = \"single\"\n",
    "}\n",
    "\n",
    "```\n",
    "\n",
    "\n",
    "#### 对象创建\n",
    "\n",
    "```kotlin\n",
    "\n",
    "//创建一个String对象\n",
    "val str = \"this is a string .\"\n",
    "//创建一个int对象\n",
    "val number = 100\n",
    "//创建一个list\n",
    "val list = mutableListOf<String>()\n",
    "\n",
    "\n",
    "```\n",
    "\n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "subslide"
    }
   },
   "source": [
    "- **安全性**   \n",
    "   kotlin中会对变量方法进行非空检测，在编译期就避免烦人的NullPointerException错误，为此kotlin中引入了两个特殊操作符号('?'和‘!!’)。而且会对kotlin进行自动类型转换，防止因为强制转换导致的类型一场。"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "fragment"
    }
   },
   "source": [
    "```kotlin\n",
    "var output: String       //定义单个类型在对其进行赋值操作的时候会对其进行非空检测，若为空则编译错误\n",
    "output = null   // 编译错误\n",
    "\n",
    "val name: String? = null    // 可空类型，可以通过在类型后面添加一个“？”来指定该类型可以为空\n",
    "println(name.length())      // 编译错误\n",
    "\n",
    "\n",
    "//闯入参数要求为String类型(非空类型)\n",
    "fun test(String:args){\n",
    "     println(args)\n",
    "}\n",
    "\n",
    "test(args!!) //可以通过在参数后添加!!来强制制定传入参数，若参数为空则抛出异常\n",
    "\n",
    "\n",
    "\n",
    "if (obj is Invoice)            //kotlin 中可以通过is来判断对象的类型，若类型判断通过，kotlin会自动将该对象转化为对应类型.\n",
    "        obj.calculateTotal()\n",
    "\n",
    "```"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "subslide"
    }
   },
   "source": [
    "- ** 互操作性**  \n",
    "   kotlin也是基于Jvm的一种语言，kotlin支持给予JVM的任意语言开发的资源库的调用，即class级别通用."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "fragment"
    }
   },
   "source": [
    "- ** 工具友好 **  \n",
    "   由于JetBrains本身就是做工具的，java级别的工具更是强大，目前支持kotlin插件的开发工具有jetBrains系列java IDE，Android Studio、Eclipse等.都是较为主流的开发工具,所以Kotlin开发的外部环境还是不错的."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "slide"
    }
   },
   "source": [
    "##  Kotlin与Java\n",
    "\n",
    "- 语法简单，易懂  \n",
    "  Kotlin中对于语法的设计更加类似于python这类的脚本语言的语法格式\n",
    "  \n",
    "  \n",
    "- 空指针安全和类型的自动转换\n",
    " 如上安全性的定义, kotlin需要对类型进行空指针校验，相对于java中比较烦人的空指针异常让人舒服很多\n",
    "  \n",
    "  \n",
    "- 支持方法和属性的扩展  \n",
    "  kotlin的方法扩展的特性可以说是一大亮点,我们可以直接针对类进行方法扩展，而不需要在特意定制某个自定义类来进行定制.\n",
    "  \n",
    "\n",
    "- lambda，高阶函数,协程，数据类(data class),inline函数等\n",
    "  kotlin特有特性，使得kotlin的使用更加的方便和简单，会在之后对部分特性进行介绍.\n",
    "\n",
    "\n",
    "- 不得不说的android findViewById()  \n",
    "  kotlin对于android findViewById的精简可谓是相当高效的，允许直接通过id名来代替控件本身.\n",
    "\n",
    "\n",
    "- kotlin于java的互操作性  \n",
    "  和java 一样kotlin也同属于jvm语言，两者直接可以通过编译成class文件直接互相调用.\n",
    "  \n",
    " \n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "slide"
    }
   },
   "source": [
    "## Kotlin的特性\n",
    "\n",
    "- **空安全**   \n",
    "   **Kotlin 的类型系统旨在消除来自代码空引用的危险，也称为Tony Hoare的《十亿美元的错误》**。许多编程语言（包括 Java）中最常见的陷阱之一是访问空引用的成员，导致空引用异常。在 Java 中， 这等同于 NullPointerException 或简称 NPE。\n",
    "\n",
    "    Kotlin 的类型系统旨在从我们的代码中消除 NullPointerException。NPE 的唯一可能的原因可能是：\n",
    "\n",
    "     - 显式调用 throw NullPointerException()\n",
    "     - 使用了 !! 操作符\n",
    "     - 外部 Java 代码导致的\n",
    "     - 对于初始化，有一些数据不一致（如一个未初始化的 this 用于构造函数的某个地方）\n",
    "\n",
    "     在 Kotlin 中，类型系统区分一个引用可以容纳 null （可空引用）还是不能容纳（非空引用）。 例如，String 类型的常规变量不能容纳 null：\n",
    "\n",
    "```kotlin\n",
    "\n",
    "var a: String = \"abc\"\n",
    "a = null // 编译错误\n",
    "\n",
    "```\n",
    "如果要允许为空，我们可以声明一个变量为可空字符串，写作 String?：\n",
    "\n",
    "```kotlin\n",
    "\n",
    "var b: String? = \"abc\"\n",
    "b = null // ok\n",
    "\n",
    "```\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "subslide"
    }
   },
   "source": [
    "\n",
    "- **DTOS(POJOs/POCOs) **  \n",
    "  java中的pojo,会为类的对象提供getter(),equals()、hashCode()、toString()，copy()等方法，简化了创建方式：\n",
    "  \n",
    "  ```kotlin\n",
    "\n",
    " //若为var类型还会提供setter方法\n",
    "  data class Customer(val name: String, val email: String)\n",
    "  ```\n",
    "\n",
    "\n",
    "\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "subslide"
    }
   },
   "source": [
    "- ***扩展* *  \n",
    "  Kotlin能够扩展一个类的新功能而无需继承该类或使用像装饰者这样的任何类型的设计模式。 这通过叫做 扩展 的特殊声明完成。Kotlin 支持 扩展函数 和 扩展属性。"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "markdown",
   "metadata": {
    "slideshow": {
     "slide_type": "slide"
    }
   },
   "source": [
    "## Kotlin 检索\n",
    "\n",
    "- Kotlin 官网  \n",
    "  http://kotlinlang.org/\n",
    "  \n",
    "- Kotlin 文档  \n",
    "   http://kotlinlang.org/docs/reference/\n",
    "   \n",
    "- Kotlin 官方博客  \n",
    "  https://blog.jetbrains.com/kotlin\n",
    "  \n",
    "- Kotlin 问题跟踪  \n",
    "  https://youtrack.jetbrains.com/issues/KT\n",
    "  \n",
    "- Kotlin 官方论坛  \n",
    "  https://discuss.kotlinlang.org/\n",
    "  \n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "metadata": {
    "slideshow": {
     "slide_type": "notes"
    }
   },
   "outputs": [
    {
     "data": {
      "image/png": "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\ngg==\n",
      "text/plain": [
       "<matplotlib.figure.Figure at 0x7f1b67fccf90>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "#!/usr/bin/env python\n",
    "# -*-encoding:utf-8-*-\n",
    "\n",
    "\n",
    "import sys,urllib\n",
    "from bs4 import BeautifulSoup\n",
    "from matplotlib import pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "u'''\n",
    "获取kotlin官方Blog中的发布数据信息,并通过图例展示.\n",
    "\n",
    "'''\n",
    "\n",
    "#解释器\n",
    "MY_MARKUP=\"lxml\"\n",
    "#最近提交的\n",
    "RECENT_POSTS_ID = \"recent-posts-2\"\n",
    "#所有文档按月份\n",
    "ARCHIVES_ID = \"archives-2\"\n",
    "#按照标签分类\n",
    "CATEGORIES_ID = \"categories-2\"\n",
    "\n",
    "#filter of archives\n",
    "ARCHIVES_FILTER_ID = 'entry-title'\n",
    "\n",
    "\n",
    "\n",
    "def parseSpecies(tagInfo):\n",
    "    u'''\n",
    "    用于解析对应项中的url.\n",
    "    :param tag:  [element.Tag] Tag标签,包裹ul,a\n",
    "    :return: 返回一个字典,key为分类,value为指向的url.\n",
    "    '''\n",
    "    dict = {}\n",
    "    tagList = tagInfo.find_all(name='li')\n",
    "    for tag in tagList:\n",
    "        url = tag.a['href']\n",
    "        name = tag.a.get_text()\n",
    "        if url and name:\n",
    "            dict[name] = url\n",
    "        # print name, url\n",
    "    return dict\n",
    "\n",
    "\n",
    "\n",
    "def getArticleInfo(url,filter):\n",
    "    '''\n",
    "    get articles' number from this url.\n",
    "    :param url:  web url\n",
    "    :return: count of articles.\n",
    "    '''\n",
    "    html=urllib.urlopen(url)\n",
    "    soup = BeautifulSoup(html,MY_MARKUP)\n",
    "    list=soup.find_all(class_=filter)\n",
    "    alist = []\n",
    "    for line in list:\n",
    "        url = line.a['href']\n",
    "        title =  line.a.get_text()\n",
    "        alist.append({\"url\":url,\"title\":title})\n",
    "    return  alist\n",
    "\n",
    "\n",
    "\n",
    "def drawHistogram(list):\n",
    "    '''\n",
    "    draw histogram for list.\n",
    "    :param list: contain name and count .\n",
    "    :return:\n",
    "    '''\n",
    "    x=[]\n",
    "    y=[]\n",
    "    for line in list:\n",
    "        x.append(line[\"title\"][0:2])\n",
    "        y.append(int(line[\"count\"]))\n",
    "    plt.bar(x=x,height=y,color='blue',width=0.5)\n",
    "    plt.show()\n",
    "\n",
    "\n",
    "\n",
    "main_html = urllib.urlopen(\"https://blog.jetbrains.com/kotlin\")\n",
    "soup = BeautifulSoup(main_html,MY_MARKUP)\n",
    "recentPosts =  soup.find(id=RECENT_POSTS_ID)\n",
    "archives =  soup.find(id=ARCHIVES_ID)\n",
    "categories = soup.find(id=CATEGORIES_ID)\n",
    "\n",
    "dic = parseSpecies(archives)\n",
    "list = []\n",
    "# print dic\n",
    "for name,url in dic.items():\n",
    "    list.append({\"title\":name,\"count\":len(getArticleInfo(url,ARCHIVES_FILTER_ID))})\n",
    "\n",
    "drawHistogram(list)\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "celltoolbar": "Slideshow",
  "kernelspec": {
   "display_name": "Python 2",
   "language": "python",
   "name": "python2"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 2
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython2",
   "version": "2.7.6"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
